#include <fstream>
#include <iostream>

#include "Commands.hpp"
#include "OrderBook.hpp"

class TradeCallback : public FeedHandler::OnNewTradeCallback
{
public:
	TradeCallback() : m_quantity(0)
	{
	}

	void operator()(const FeedHandler::Trade & trade)
	{
		if (m_quantity != 0 && m_recentPrice == trade.price)
		{
			m_quantity += trade.quantity;
		}
		else
		{
			m_quantity = trade.quantity;
			m_recentPrice = trade.price;
		}

		std::cout << "Trade: " << trade.quantity << ", " << trade.price
				  << " => " << m_quantity << "@" << m_recentPrice
				  << std::endl;
	}

private:
	double m_recentPrice;
	uint32 m_quantity;
};

int main(int argc, char * argv[])
{
	FeedHandler::OnNewTradeCallback::Ptr cb(new TradeCallback());

	FeedHandler::OrderBook ob(cb); // here we're loosing ownership of callback because of auto_ptr. It's better tot use boost::shared_ptr here
	FeedHandler::CommandFactory factory;

	// reading file
	std::ifstream infile(argv[1], std::ios::in);
	std::string line;
	uint32 counter = 0;

	while (std::getline(infile, line))
	{
		try
		{
			FeedHandler::Command::Ptr pCmd = factory.create(line);

			pCmd->execute(ob);

			std::cout << "midquote: " << ob.calculateMidQuote() << std::endl;

			if (++counter % 10 == 0)
			{
				std::cout << ob.toString() << std::endl;
			}
		}
		catch (std::exception & e)
		{
			std::cerr << "exception has been caught: " << e.what() << std::endl
				<< "command: " << line << std::endl;
		}
		catch (...)
		{
			std::cerr << "An unknown exception has been caught" << std::endl
				<< "command: " << line << std::endl;
		}
	}

	return 0;
}
